[WC-3537]: Fix resizing issue with Signature pad - #2375
Conversation
This comment has been minimized.
This comment has been minimized.
AI Code Review
What was reviewed
Skipped (out of scope): CI check status: command required approval — could not be verified automatically. Findings🔶 Medium — Primary bug fix (resize handler) has no test coverageFile: it("calls pad.off(), resizes canvas, pad.redraw(), then pad.on() on resize", () => {
let observerCallback: ResizeObserverCallback | undefined;
(global.ResizeObserver as jest.Mock).mockImplementation((cb: ResizeObserverCallback) => {
observerCallback = cb;
return { observe: jest.fn(), disconnect: jest.fn() };
});
stubContainerDimensions(800, 400);
const imageSource = buildImageSource(); // unavailable → pad initialises
render(<TestHarness imageSource={imageSource} />);
const padInstance = MockSignaturePad.mock.instances[0] as any;
jest.clearAllMocks();
act(() => {
observerCallback!([], {} as ResizeObserver);
});
const offIdx = (padInstance.off as jest.Mock).mock.invocationCallOrder[0];
const drawIdx = (padInstance.redraw as jest.Mock).mock.invocationCallOrder[0];
const onIdx = (padInstance.on as jest.Mock).mock.invocationCallOrder[0];
expect(offIdx).toBeLessThan(drawIdx);
expect(drawIdx).toBeLessThan(onIdx);
});
|
Bug fixes
Strokes stop registering after widget resize
When the widget container was resized mid-stroke (e.g., opening browser DevTools),
signature_padleft its internal_drawingStrokeflag astruepermanently. Thepointeruplistener had been removed from the window, sostrokeEndnever fired and every subsequentpointerdownwas silently dropped. Fixed by callingpad.off()before resizing the canvas andpad.on()after — this resets_drawingStrokeand re-registers the pointer listeners.Canvas initializes at wrong size
The canvas was initialized at the HTML default size (300×150) when the
ResizeObserverfired beforeimageSourcebecame available. On init, the pad now reads the container's actual dimensions directly before instantiatingSignaturePad.Code quality improvements
useSignaturePadowns theResizeObserver— the hook now callsuseResizeObserverinternally and returns acontainerRefalongsidecanvasRef.SizeContainerno longer manages the observer or exposes anonResizecallback; it is a plainforwardRefcomponent. This removes the prop-threading indirection, and theparentElementlookup.pad.redraw()replaces manualtoData()/clear()/fromData()— the library's own method handles the snapshot internally.useMemowithif/elsechains with aRecord<PenTypeEnum, Options>constant and agetPenOptionshelper; type safety is enforced at the call site.isSignatureInitializedref removed — redundant alongside the existingsignaturePadRef === nullguard.ifblocks into a single expression.